<?php

abstract class MACAbstractModel extends Zend_Db_Table_Abstract implements IAbstractModel{
	
	protected static $_instance;
	protected $_name;
	protected $_primary;
	protected $_database;
	protected $_host;
	protected $_dbTable;
	protected $logger;
	
	public function __construct($table, $primary) {
		$c = ConfigFactory::getInstance()->getConfig();
		
		$this->logger = LogFactory::getInstance()->getLogger();	
		
		$this->_database = $c->database->dbname;
		$this->_host = $c->database->dbhost;
		$this->_primary = $primary;
		$this->_name = $table;
	
		$infos['params']['charset'] = 'utf8';
		$infos['adapter'] = 'pdo_mysql';
		$infos['params']['dbname'] = $c->database->dbname;
		$infos['params']['host'] = $c->database->dbhost;
		$infos['params']['username'] = $c->database->dbusername;
		$infos['params']['password'] = $c->database->dbpassword;
	
		$config = new Zend_Config($infos);
		$conf = Zend_Db::factory($config);
		Zend_Db_Table::setDefaultAdapter($conf);
		parent::__construct($conf);
	}
	
	
	/**
	 * **********************************************************************************
	 * INTERNAL DB MODEL METHODS
	 * **********************************************************************************
	 */
			
	public function fetchAll($where = null, $order = null, $count = null, $offset = null) {
		try{
			if(is_array($where)) $where = $this->makeZendArrayWhere($where);
	
			return parent::fetchAll($where,$order,$count,$offset);
		}catch ( Exception $e ){
			$logger = OmcLoggerFactory::getLogger();
			$logger->critical("304","Can't fetch all rows",$e);
			throw $e;
		}
	}
	
	public function makeZendArrayWhere(array $array) {
		foreach ($array as $key => $value ){
			if (preg_match("/^[^ ]+ [^ ]+ [?]$/", $key))
			{
				$arrayTmp[$key] = $value;
			}
			else
			{
				$arrayTmp[$key . ' = ?'] = $value;
			}
		}
		return $arrayTmp;
	}
	
	
	public function setDbTable($dbTable)
	{
		if (is_string($dbTable)) {
			$dbTable = new $dbTable($this->_name, $this->_primary);
		}
		if (!$dbTable instanceof Zend_Db_Table_Abstract) {
			$logger = OmcLoggerFactory::getLogger();
			$logger->critical("302","Invalid table data gateway provided",$e);
			throw new OmcException("Invalid table data gateway provided, see exception message : ".$e->getMessage(),"302");
		}
		$this->_dbTable = $dbTable;
		return $this;
	}
	
	public function __set($name, $value)
	{
		$method = 'set' . $name;
		if (('mapper' == $name) || !method_exists($this, $method)) {
			$logger = OmcLoggerFactory::getLogger();
			$logger->critical("303","Invalid set property",$e);
			throw new OmcException("Invalid set property, see exception message : ".$e->getMessage(),"303");
		}
		$this->$method($value);
	}
	
	public function __get($name)
	{
		$method = 'get' . $name;
		if (('mapper' == $name) || !method_exists($this, $method)) {
			throw new Exception('Invalid get property');
		}
		return $this->$method();
	}
	
	public function fetchAllPaginator($where = null, $order = null, $count = null, $offset = null) {
		try{
			if(is_array($where)){
				$where = $this->makeZendArrayWhere($where);
			}
			if (!($where instanceof Zend_Db_Table_Select)) {
				$select = $this->select();
					
				if ($where !== null) {
					$this->_where($select, $where);
				}
					
				if ($order !== null) {
					$this->_order($select, $order);
				}
					
				if ($count !== null || $offset !== null) {
					$select->limit($count, $offset);
				}
					
			} else {
				$select = $where;
			}
			$sql = $select->__toString();
			$logger = OmcLoggerFactory::getLogger();
			$logger->debug('SQL resuest is: ' . $sql);
			$paginator = Zend_Paginator::factory($select);
			return $paginator;
	
		}catch ( Exception $e ){
			$logger = OmcLoggerFactory::getLogger();
			$logger->critical("301","Can't fetch all rows with pagination, see exception message.",$e);
			throw new OmcException("Can't fetch all rows with pagination, see exception message : ".$e->getMessage(),"301");
		}
	}
	
	public function fetchAllToArrayPaginator($where = null, $order = null, $offset = null) {
		$result = $this->fetchAllPaginator($where,$order,$offset);
		return $result;
	}
	
	public function fetchAllToArray($where = null, $order = null, $offset = null) {
		$result = $this->fetchAll($where,$order,$offset);
		return $this->toArrayResult($result);
	}
	
} 